home *** CD-ROM | disk | FTP | other *** search
/ SGI Developer Toolbox 6.1 / SGI Developer Toolbox 6.1 - Disc 4.iso / src / haeberli / libgutil / movie.c < prev    next >
C/C++ Source or Header  |  1994-08-01  |  5KB  |  224 lines

  1. /*
  2.  * Copyright 1992, 1993, 1994, Silicon Graphics, Inc.
  3.  * All Rights Reserved.
  4.  *
  5.  * This is UNPUBLISHED PROPRIETARY SOURCE CODE of Silicon Graphics, Inc.;
  6.  * the contents of this file may not be disclosed to third parties, copied or
  7.  * duplicated in any form, in whole or in part, without the prior written
  8.  * permission of Silicon Graphics, Inc.
  9.  *
  10.  * RESTRICTED RIGHTS LEGEND:
  11.  * Use, duplication or disclosure by the Government is subject to restrictions
  12.  * as set forth in subdivision (c)(1)(ii) of the Rights in Technical Data
  13.  * and Computer Software clause at DFARS 252.227-7013, and/or in similar or
  14.  * successor clauses in the FAR, DOD or NASA FAR Supplement. Unpublished -
  15.  * rights reserved under the Copyright Laws of the United States.
  16.  */
  17. /*
  18.  *    movie -
  19.  *        File support for movie files
  20.  *
  21.  *            Paul Haeberli - 1992 
  22.  *
  23.  *    exports
  24.  *
  25.     void sizeofmovie(inf,xsize,ysize,nframes)
  26.     int readframe(inf,cbuf,maxsize)
  27.     void writemovieheader(outf,ixsize,iysize,nframes)
  28.     void writeframe(outf,cbuf,nbytes)
  29.     void createmovie(outf,ixsize,iysize,bitsperpix)
  30.     void addframe(outf,lbuf,ixsize,iysize)
  31.     statmovie(inf)
  32.  *
  33.  */
  34. #include "stdio.h"
  35. #include "movie.h"
  36.  
  37. /*
  38.  *    support for reading movie files
  39.  */
  40. void sizeofmovie(inf,xsize,ysize,nframes)
  41. FILE *inf;
  42. int *xsize, *ysize, *nframes;
  43. {
  44.     int magic;
  45.  
  46.     res_fseek(inf,0,0);
  47.     res_fread(&magic,sizeof(int),1,inf);
  48.     if(magic != MOVMAGIC) {
  49.         fprintf(stderr,"expmov: bad magic in input file %x\n",magic);
  50.         exit(1);
  51.     }
  52.     res_fread(nframes,sizeof(int),1,inf);
  53.     res_fread(xsize,sizeof(int),1,inf);
  54.     res_fread(ysize,sizeof(int),1,inf);
  55. }
  56.  
  57. int readframe(inf,cbuf,maxsize)
  58. FILE *inf;
  59. unsigned char *cbuf;
  60. int maxsize;
  61. {
  62.     int nbytes;
  63.  
  64.     res_fread(&nbytes,sizeof(int),1,inf);
  65.     if(nbytes>maxsize) {
  66.         fprintf(stderr,"readframe %d more than max %s\n",nbytes,maxsize);
  67.         return;
  68.     }
  69.     res_fread(cbuf,nbytes,1,inf);
  70.     return nbytes;
  71. }
  72.  
  73. /* 
  74.  *    support for writing movie files
  75.  */
  76. void writemovieheader(outf,ixsize,iysize,nframes)
  77. FILE *outf;
  78. int ixsize, iysize, nframes;
  79. {
  80.     int pos, magic;
  81.     int xtiles, ytiles;
  82.     int xsize, ysize;
  83.  
  84.     xtiles = ixsize/4;
  85.     ytiles = iysize/4;
  86.     xsize = xtiles*4;
  87.     ysize = ytiles*4;
  88.  
  89.     pos = ftell(outf);
  90.     fseek(outf,0,0);
  91.     magic = MOVMAGIC;
  92.     fwrite(&magic,sizeof(int),1,outf);
  93.     fwrite(&nframes,sizeof(int),1,outf);
  94.     fwrite(&xsize,sizeof(int),1,outf);
  95.     fwrite(&ysize,sizeof(int),1,outf);
  96.     if(pos<(4*sizeof(int)))
  97.     pos = 4*sizeof(int);
  98.     fseek(outf,pos,0);
  99.     fflush(outf);
  100. }
  101.  
  102. void writeframe(outf,cbuf,nbytes)
  103. FILE *outf;
  104. unsigned char *cbuf;
  105. int nbytes;
  106. {
  107.     fwrite(&nbytes,sizeof(int),1,outf);
  108.     fwrite(cbuf,nbytes,1,outf);
  109.     fflush(outf);
  110. }
  111.  
  112. static float p = 1.0;
  113. static float step = 1.0;
  114. static int mxsize, mysize;
  115. static float mbitsperpix;
  116. static int mframeno;
  117.  
  118. void createmovie(outf,ixsize,iysize,bitsperpix)
  119. FILE *outf;
  120. int ixsize, iysize;
  121. float bitsperpix;
  122. {
  123.     mxsize = ixsize;
  124.     mysize = iysize;
  125.     mbitsperpix = bitsperpix;
  126.     mframeno = 0;
  127.     writemovieheader(outf,mxsize,mysize,0);
  128. }
  129.  
  130. #define MAXTHRESH_FLAT  (12)        /* make bigger for more flat 4x4 areas */
  131. #define THRESH_CHROMA   (15)        /* controls bw/color for flat 4x4s */
  132. #define THRESH_FLAT     (1)         /* make bigger for more flat 4x4 areas */
  133. #define THRESH_EDGE     (2)         /* make smaller for more detail */
  134.  
  135. static int sthc, sthf, sthe, paramset;
  136.  
  137. movieparams(thc,thf,the)
  138. int thc, thf, the;
  139. {
  140.     sthc = thc;
  141.     sthf = thf;
  142.     sthe = the;
  143.     paramset = 1;
  144. }
  145.  
  146. void addframe(outf,lbuf,ixsize,iysize)
  147. FILE *outf;
  148. unsigned long *lbuf;
  149. int ixsize, iysize;
  150. {
  151.     int cbuflen, wbuflen;
  152.     unsigned char *cbuf;
  153.     int thc, thf, the;
  154.     int maxbytes;
  155.  
  156.     if(ixsize != mxsize || iysize != mysize) {
  157.     fprintf(stderr,"addframe: all images must be same size\n");
  158.     return;
  159.     }
  160.     cbuflen = ixsize*iysize;
  161.     cbuf = (unsigned char *)malloc(cbuflen*sizeof(char));
  162.     step = 1.0;
  163.  
  164.     if(paramset) {
  165.     thc = sthc;
  166.     thf = sthf;
  167.     the = sthe;
  168.     wbuflen = compress(lbuf,ixsize,iysize,cbuf,cbuflen,thc,thf,the);
  169.     } else {
  170.     maxbytes = (ixsize*iysize*mbitsperpix)/8;
  171.     while(1) {
  172.         thc = THRESH_CHROMA;
  173.         thf = p*THRESH_FLAT;
  174.         if(thf>MAXTHRESH_FLAT)
  175.         thf = MAXTHRESH_FLAT;
  176.         the = p*THRESH_EDGE;
  177.         wbuflen = compress(lbuf,ixsize,iysize,cbuf,cbuflen,thc,thf,the);
  178.  
  179.         if(wbuflen<=maxbytes) {
  180.     #define DEBUG
  181.     #ifdef DEBUG
  182.         printf("used chroma %d flat %d edge %d P is %f\n", thc, thf, the,p);
  183.     #endif
  184.         step = 0.5;
  185.         p = p-step;
  186.         if(p<0.0)
  187.             p = 0.0;
  188.         break;
  189.         }
  190.         p = p+step;
  191.     }
  192.     }
  193.     writeframe(outf,cbuf,wbuflen);
  194.     mframeno++;
  195.     writemovieheader(outf,ixsize,iysize,mframeno);
  196.     free(cbuf);
  197. }
  198.  
  199. /*
  200.  *    print info about a movie file
  201.  */
  202. void statmovie(inf)
  203. FILE *inf;
  204. {
  205.     int xsize, ysize, nframes;
  206.     int nbytes, npix, bypf, pos;
  207.     float bpp;
  208.  
  209.     pos = ftell(inf);
  210.     sizeofmovie(inf,&xsize,&ysize,&nframes);
  211.     fseek(inf,pos,0);
  212.     nbytes = sizeoffile(inf);
  213.     npix = xsize*ysize*nframes;
  214.     bpp = (nbytes*8.0)/npix;
  215.     bypf = nbytes/nframes;
  216.     fprintf(stderr,"movie size %d by %d pixels, %d frames\n",xsize,ysize,nframes);
  217.     fprintf(stderr,"frames per second: %d\n",10);
  218.     if(nframes>0) {
  219.     fprintf(stderr,"average bits per pixel: %f\n",bpp);
  220.     fprintf(stderr,"average bytes per frame: %d\n",bypf);
  221.     fprintf(stderr,"average bytes per second: %d\n",10*bypf);
  222.     }
  223. }
  224.